﻿using System.Windows.Markup;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input;
using Om.Camera;
using Om.Core.Extension;
using Om.Core.Singleton;
using TouchSocket.Sockets;

namespace OptoMeasure.Views;

public partial class CameraViewModel : ObservableObject
{
    [ObservableProperty] private string _title;
    [ObservableProperty] private bool _isConnected = true;
    [ObservableProperty] private ImageSource _imageSource;
    [ObservableProperty] private string _info;

    [ObservableProperty] private bool _isFullScreenDisplay = false;

    public IBaseCamera Camera { get; set; }
    private int _rotateAngel = 0;
    public bool CanSetExposure { get; set; }

    //public CameraViewModel()
    //{
    //    Title = "相机";
    //}

    public CameraViewModel(string cameraTitle,IBaseCamera camera)
    {
        Camera = camera;
        CanSetExposure = camera.CanSetExposure;

        Title = cameraTitle;
        _rotateAngel = DevicesConfig.Instance.CameraRotateAngle.ContainsKey(Title)
            ? DevicesConfig.Instance.CameraRotateAngle[Title] : 0;
        Camera.ConnectionChanged+= CameraOnConnectionChanged; 
        Camera.FrameReceived += CameraOnFrameReceived;
    }

    [RelayCommand]
    private async Task SetExposureVal()
    {
        var view = new CameraExpSetView(Camera);
        view.ShowDialog();
    }

    [RelayCommand]
    private async Task Capture()
    {
        var path = CaptureHelper.GetFileFullPath(Title);
        await Camera.Capture(path);
    }

    [RelayCommand]
    private void Rotate()
    {
        _rotateAngel += 90;
        _rotateAngel %= 360;

        DevicesConfig.Instance.CameraRotateAngle[Title] = _rotateAngel;
    }


    private void CameraOnFrameReceived(byte[] obj)
    {
        ImageSource = ByteArrayToBitmapImage(obj,_rotateAngel);
        CameraUdpManager.Instance.Send(Title,obj);
    }

    private void CameraOnConnectionChanged(object? sender, bool e)
    {
        IsConnected = e;
    }

    private BitmapImage ByteArrayToBitmapImage(byte[] bytes,int angle)
    {
        if (bytes == null || bytes.Length == 0)
            return null;

        var bitmapImage = new BitmapImage();
        using (var stream = new System.IO.MemoryStream(bytes))
        {
            bitmapImage.BeginInit();
            bitmapImage.CacheOption = BitmapCacheOption.OnLoad;
            bitmapImage.StreamSource = stream;
            bitmapImage.EndInit();
        }
        if (angle != 0)
        {
            var rotatedImage = new TransformedBitmap(bitmapImage, new RotateTransform(angle));
            
            return TransformedBitmapToBitmapImage(rotatedImage);
        }

        bitmapImage.Freeze(); // 冻结对象以提高性能（线程安全）
        return bitmapImage;
    }
    private BitmapImage TransformedBitmapToBitmapImage(TransformedBitmap transformedBitmap)
    {
        if (transformedBitmap == null)
            return null;

        var bitmapImage = new BitmapImage();
        using (var stream = new System.IO.MemoryStream())
        {
            var encoder = new PngBitmapEncoder(); // 使用 PNG 编码器
            encoder.Frames.Add(BitmapFrame.Create(transformedBitmap));
            encoder.Save(stream);

            bitmapImage.BeginInit();
            bitmapImage.CacheOption = BitmapCacheOption.OnLoad;
            bitmapImage.StreamSource = new System.IO.MemoryStream(stream.ToArray());
            bitmapImage.EndInit();
        }

        bitmapImage.Freeze();
        return bitmapImage;
    }
}